Tienery:Operating with Maps
To make my life a little easier, I tend to use the haxe.Map ''class to help retrieve assets, and this is particularly true when you use the same font format over and over again and don't want to repeat the code all the time. It also makes the game a lot more efficient. What Maps do In programming, a Map (aka Hashtable) is a table of two columns, one is a key, and another the associated value. The underlying code will take two types, the type for the key, and the type for the value, and will determine the size of each and then allocate the map on the heap. For those of you who do not know, the heap is basically memory that hangs around for the entire lifespan of an application, while the stack is virtual memory and often faster to access. It is more efficient than most modes of data access since it does less calculations to retrieve a result. This is not necessarily true if the Map is small, but in large quantities Map's have a significant advantage over Array's, for example. Using the Map To use a Map, we use the following code to instantiate one: private var _fonts:Map = new Map(); Then we can set a value: _fonts.set("normal", new TextFormat(Assets.getFont("font/opensans.ttf").fontName, 11, 0x000000)); In the example above, "normal" is associated with the Open Sans font, with a size of 11 pixels and the colour black. To use it on a TextField, all I would have to do is this: private var _myTextField:TextField; _myTextField = new TextField(); _myTextField.defaultTextFormat = _fonts.get("normal"); This certainly makes it easier, but if I'm not using enough formats, then I could always just use an Array. Where Map's are most useful Map's are most useful with the Tilesheet class in the OpenFL framework. The use of Map's will make it easier to draw actual Map's onto the game screen. Take the following example as reference: _tiles = new Tilesheet(Assets.getBitmapData("img/myTilemap.png")); _map = new Map(); _map.set("grass", _tiles.addTileRect(new Rectangle(0, 0, 32, 32)); _map.set("snow", _tiles.addTileRect(new Rectangle(32, 0, 32, 32)); _map.set("gravel", _tiles.addTileRect(new Rectangle(64, 0, 32, 32)); ... public function drawTile(g:Graphics, location:Point, index:Int):Void { _tiles.drawTiles(g, location.y, index); } ... _myMap.drawTile(_mySprite.graphics, new Point(0, 0), _map.get("snow")); Let's split this up into individuals lines and understand what is going on. _tiles = new Tilesheet(Assets.getBitmapData("img/myTilemap.png")); Firstly, I have created a new Tilesheet and have given it an image to work from. This will be used later when I set up the Tilesheet to specify which tile is which. _map = new Map(); Here I am creating a new Map and giving it the key type ''String ''and the value type ''Int. _map.set("grass", _tiles.addTileRect(new Rectangle(0, 0, 32, 32)); _map.set("snow", _tiles.addTileRect(new Rectangle(32, 0, 32, 32)); _map.set("gravel", _tiles.addTileRect(new Rectangle(64, 0, 32, 32)); This is where things may sound a bit more complicated. So this is where Map's become particularly useful, because the addTileRect function of the Tilesheet class returns the index of the newly set tile. The Rectangle specifies the bounds of the tile, so in the example above, each tile is 32x32 pixels. The first tile is grass, the second tile is snow and the third is gravel. public function drawTile(g:Graphics, location:Point, index:Int):Void { _tiles.drawTiles(g, location.y, index); } In this class, I am creating a function which will allow me to draw a Tile onto the graphical surface of a Sprite. It asks for a location and an index. Inside the function, we have one function that will draw a tile onto the graphical surface that we pass in, accessing where to locate this tile and what index. There are other optional parameters in this drawTiles() ''function, but I decided to omit them. _myMap.drawTile(_mySprite.graphics, new Point(0, 0), _map.get("snow")); Now I am taking advantage of this function and drawing a tile to the graphics property of ''_mySprite. The location that I place is (0,0) and the tile I want it to be is going to be "snow". This makes at least my life easier so I don't have to refer to the tileset everytime I want to get a specific tile. Map's are not necessarily useful once you start using a Tile Map editor, for example. But if you were drawing a tile map programmatically, this is how I would do it. Conclusion Map's a very efficient, and when used with large quantities of data, they can be particularly more efficient than dealing with arrays. As in the above example, they can be useful for drawing maps and even reducing tedious repetition in that you can reduce the creation of additional TextFormat's for example.